package hackathon.light.up;

import java.util.ArrayList;
import java.util.HashMap;

import android.database.MatrixCursor;
import android.util.Log;
import android.view.MotionEvent;

import com.e3roid.E3Scene;
import com.e3roid.drawable.Shape;
import com.e3roid.event.SceneUpdateListener;
import com.e3roid.event.ShapeEventListener;

public class Grid {

	private ArrayList<Shape> shapes;
	public static ArrayList<Laser> lasers;
	// private ArrayList<Laser> elements;
	public static Element[][] elementMatrix;

	private int grid_row, grid_col, grid_offset, width, height, grid_width,
			grid_height;
	// cell dimension, top left corner of the grid
	public static int CELL_SIZE, POSX, POSY, THICKNESS,ROW, COL;
	private E3Scene scene;
	
	public static Grid grid;

	/*
	 * Background constructor
	 */

	public Grid(int w, int h, int row, int col, int thickness, int gridOffset) {
		this.grid_col = col;
		this.grid_row = row;
		
		this.width = w;
		THICKNESS = thickness;
		this.scene = scene;
		this.height = h;
		this.grid_offset = gridOffset;

		Log.d("GRID : ", "min " + height + " " + (100 - gridOffset) + " "
				+ ((100 - gridOffset) * height / (100 * row)) + " " + width
				/ col + "");
		CELL_SIZE = (int) Math.min(((100 - gridOffset) * height / (100 * row)),
				width / col);
		grid_width = col * CELL_SIZE;
		grid_height = row * CELL_SIZE;
		POSX = (width - grid_width) / 2;
		POSY = height * gridOffset / 100
				+ ((100 - gridOffset) * height / 100 - grid_height) / 2;
		shapes = new ArrayList<Shape>();
		
		this.elementMatrix = new Element[grid_row + 2][grid_col + 2];
		lasers = new ArrayList<Laser>();

		lasers.add(new Laser(3, 0, LightDirection.E, 2));
		elementMatrix[4][1]= lasers.get(0);
		lasers.add(new Laser(3, 5, LightDirection.W, 4));
		elementMatrix[4][6]= lasers.get(1);
		createGrid();
		addPadding();
		Grid.grid = this;
	}

	private void addPadding() {
		for (int i = 0; i < grid_col + 2; i++) {
			elementMatrix[0][i] = new MattElement(0, i);
			elementMatrix[grid_row + 1][i] = new MattElement(grid_row + 1, i);
		}
		for (int i = 0; i < grid_row + 2; i++) {
			elementMatrix[i][0] = new MattElement(i, 0);
			elementMatrix[i][grid_col + 1] = new MattElement(i, grid_col + 1);
		}

		elementMatrix[4][3] = new DoubleMirror(3, 2, LightDirection.W);
	}
	
	public void update(E3Scene scene) {
		
		this.scene = scene;
				
		update();		
	}

	
	public void update() {
		
		for (int i = 0; i < lasers.size(); i++) {
			int next_col = lasers.get(i).col
					+ MapDirection
							.getNextCol(lasers.get(i).lightSources.get(0).direction);
			int next_row = lasers.get(i).row
					+ MapDirection
							.getNextRow(lasers.get(i).lightSources.get(0).direction);
			while (elementMatrix[next_row + 1][next_col + 1] == null) {
				next_col += MapDirection.getNextCol(lasers.get(i).lightSources
						.get(0).direction);
				next_row += MapDirection.getNextRow(lasers.get(i).lightSources
						.get(0).direction);
			}
			lasers.get(i).lightSources.get(0).drawLight(next_row, next_col);

			elementMatrix[next_row+1][next_col+1].update(lasers.get(i).lightSources.get(0));
		}
		draw(scene);
	}

	public void draw() {
		for (int i = 0; i < shapes.size(); i++)
			scene.getTopLayer().add(shapes.get(i));
	}

	
	public void draw(E3Scene scene) {
		this.scene = scene;
		draw();
		for (int i = 0; i < shapes.size(); i++)
			scene.getTopLayer().add(shapes.get(i));
		for (int i = 0; i < lasers.size(); i++) {
			lasers.get(i).draw(scene);
		}

		for (int i = 0; i < grid_row + 2; i++) {
			for (int j = 0; j < grid_col + 2; j++) {
				if (elementMatrix[i][j] != null)
					elementMatrix[i][j].draw(scene);
			}
		}
	}
	
	private void createGrid() {

		// lines
		shapes.add(createLine(POSX, POSY, THICKNESS, grid_height, 1, 1, 1, 1));

		Log.d("cell_size", CELL_SIZE + "");
		for (int i = 0; i < grid_col; i++) {
			shapes.add(createLine(POSX + (i + 1) * CELL_SIZE - THICKNESS, POSY,
					THICKNESS, grid_height, 1, 1, 1, 1));
		}

		shapes.add(createLine(POSX, POSY, grid_width, THICKNESS, 1, 1, 1, 1));

		for (int i = 0; i < grid_row; i++) {

			shapes.add(createLine(POSX, POSY + (i + 1) * CELL_SIZE - THICKNESS,
					grid_width, THICKNESS, 1, 1, 1, 1));
		}
	}

	public ArrayList<Shape> getGrid() {
		return shapes;
	}

	public Shape createLine(int x, int y, int w, int h, float r, float b,
			float g, float a) {

		Shape s = new Shape(x, y, w, h);
		s.setColor(r, g, b, a);
		return s;
	}
}
